package io.dy.guarded_extend;

/**
 * @author dmj
 * @date 2024年03月22日 下午4:08
 * 保护性暂停 - 共享类 一个线程等待另一个线程结果
 */
@SuppressWarnings("all")
public class GuardedObject<Res> {

    /**
     * 唯一标识
     */
    private final Integer id;

    /**
     * 结果
     */
    private Res value;

    /**
     * 获取结果
     * @return
     */
    public synchronized Res getValue(){
        //判断没有结果 就进入等待
        while (value == null){
            try {
                this.wait();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }

        //有结果直接返回
        return value;
    }


    /**
     * 获取结果 -- 带超时参数
     * @return
     */
    public synchronized Res getValue(long timeout){
        //开始时间
        long begin = System.currentTimeMillis();

        //经历时间
        long passedTime = 0;
        //判断没有结果 就进入等待
        while (value == null){
            //判断经历时间是否大于等于超时时间 若是 直接退出
            if(passedTime >= timeout){
                break;
            }
            try {
                //这边等待时间是多少比较重要
                this.wait(timeout - passedTime);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }

            //求得经历时间
            passedTime = System.currentTimeMillis() - begin;
        }

        //有结果直接返回
        return value;
    }

    /**
     * 产生结果
     * @param res
     */
    public synchronized void generate(Res res){
        //给结果成员赋值
        this.value = res;
        this.notifyAll();
    }


    public GuardedObject(Integer id) {
        this.id = id;
    }

    public Integer getId() {
        return id;
    }

}
